import { ref, reactive } from 'vue'
import { ElMessage } from 'element-plus'
import api from '@/utils/api'
import type { ApiResponse, PaginatedResponse, PaginationParams } from '@/types/api'

export interface UseApiOptions {
  immediate?: boolean
  showMessage?: boolean
  showLoading?: boolean
}

export function useApi<T = any>(
  url: string,
  options: UseApiOptions = {}
) {
  const {
    immediate = false,
    showMessage = true,
    showLoading = true
  } = options

  const data = ref<T | null>(null)
  const loading = ref(false)
  const error = ref<string | null>(null)

  const execute = async (params?: any): Promise<T | null> => {
    try {
      loading.value = true
      error.value = null

      const config = {
        headers: {
          showLoading: showLoading
        }
      }

      const response = await api.get(url, { params, ...config })
      
      if (response.data.success) {
        data.value = response.data.data
        return response.data.data
      } else {
        throw new Error(response.data.message || '请求失败')
      }
    } catch (err: any) {
      const errorMessage = err.response?.data?.message || err.message || '请求失败'
      error.value = errorMessage
      
      if (showMessage) {
        ElMessage.error(errorMessage)
      }
      
      return null
    } finally {
      loading.value = false
    }
  }

  if (immediate) {
    execute()
  }

  return {
    data,
    loading,
    error,
    execute
  }
}

export function usePaginatedApi<T = any>(
  url: string,
  options: UseApiOptions = {}
) {
  const {
    immediate = false,
    showMessage = true,
    showLoading = true
  } = options

  const data = ref<T[]>([])
  const loading = ref(false)
  const error = ref<string | null>(null)
  const pagination = reactive({
    page: 1,
    pageSize: 10,
    total: 0,
    totalPages: 0
  })

  const execute = async (params?: PaginationParams & Record<string, any>): Promise<T[] | null> => {
    try {
      loading.value = true
      error.value = null

      const requestParams = {
        page: pagination.page,
        page_size: pagination.pageSize,
        ...params
      }

      const config = {
        headers: {
          showLoading: showLoading
        }
      }

      const response = await api.get(url, { params: requestParams, ...config })
      
      if (response.data.success) {
        const responseData = response.data.data as PaginatedResponse<T>
        
        data.value = responseData.results
        pagination.total = responseData.total
        pagination.totalPages = responseData.total_pages
        pagination.page = responseData.page
        pagination.pageSize = responseData.page_size

        return responseData.results
      } else {
        throw new Error(response.data.message || '请求失败')
      }
    } catch (err: any) {
      const errorMessage = err.response?.data?.message || err.message || '请求失败'
      error.value = errorMessage
      
      if (showMessage) {
        ElMessage.error(errorMessage)
      }
      
      return null
    } finally {
      loading.value = false
    }
  }

  const refresh = () => {
    execute()
  }

  const changePage = (page: number) => {
    pagination.page = page
    execute()
  }

  const changePageSize = (pageSize: number) => {
    pagination.pageSize = pageSize
    pagination.page = 1
    execute()
  }

  if (immediate) {
    execute()
  }

  return {
    data,
    loading,
    error,
    pagination,
    execute,
    refresh,
    changePage,
    changePageSize
  }
}

export function useMutation<T = any, P = any>(
  mutationFn: (params: P) => Promise<ApiResponse<T>>,
  options: UseApiOptions = {}
) {
  const {
    showMessage = true,
    showLoading = true
  } = options

  const data = ref<T | null>(null)
  const loading = ref(false)
  const error = ref<string | null>(null)

  const mutate = async (params: P): Promise<T | null> => {
    try {
      loading.value = true
      error.value = null

      const response = await mutationFn(params)
      
      if (response.success) {
        data.value = response.data || null
        
        if (showMessage && response.message) {
          ElMessage.success(response.message)
        }
        
        return response.data || null
      } else {
        throw new Error(response.message || '操作失败')
      }
    } catch (err: any) {
      const errorMessage = err.response?.data?.message || err.message || '操作失败'
      error.value = errorMessage
      
      if (showMessage) {
        ElMessage.error(errorMessage)
      }
      
      return null
    } finally {
      loading.value = false
    }
  }

  return {
    data,
    loading,
    error,
    mutate
  }
}
